package com.hr.system.service.impl;


import com.alibaba.excel.EasyExcel;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.hr.common.retrun.R;
import com.hr.common.utils.EntityConvertUtil;
import com.hr.common.utils.MenuUtil;
import com.hr.emp.param.EmpAdd;
import com.hr.emp.param.EmpPage;
import com.hr.system.entity.SysDept;
import com.hr.system.entity.SysRole;
import com.hr.system.entity.SysUser;
import com.hr.system.entity.SysUserRole;
import com.hr.system.entity.dto.SysUserDto;
import com.hr.system.entity.vo.LoginUser;
import com.hr.system.entity.vo.SysUserVO;
import com.hr.system.entity.vo.UserExcel;
import com.hr.system.enums.SysUserTypeEnums;
import com.hr.system.mapper.SysDeptMapper;
import com.hr.system.mapper.SysRoleMapper;
import com.hr.system.mapper.SysUserMapper;
import com.hr.system.mapper.SysUserRoleMapper;
import com.hr.system.service.SysUserService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import lombok.extern.slf4j.Slf4j;
import org.checkerframework.checker.units.qual.A;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import javax.servlet.ServletOutputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author hr
 * @since 2024-04-19
 */
@Service
public class SysUserServiceImpl implements SysUserService {

    @Autowired
    private SysUserMapper sysUserMapper;
    @Autowired
    private SysRoleMapper sysRoleMapper;
    @Autowired
    private SysUserRoleMapper sysUserRoleMapper;
    @Resource
    private SysDeptMapper sysDeptMapper;


    @Override
    public LoginUser login(SysUser paramUser) {
        SysUser resUser = sysUserMapper.selectOne(Wrappers.<SysUser>lambdaQuery()
                .eq(true, SysUser::getUserName, paramUser.getUserName())
                .eq(true, SysUser::getPassword, paramUser.getPassword())
        );

        if(resUser!=null&&resUser.getState()==0){  //不是禁用状态才可以登录
            LoginUser loginUser = new LoginUser();
            resUser.setPassword(null);
            loginUser.setUser(resUser);
            SysRole sysRole = sysRoleMapper.selectById(sysUserRoleMapper.selectOne(Wrappers.<SysUserRole>lambdaQuery()
                     .eq(SysUserRole::getUserId,resUser.getId())).getRoleId());
            loginUser.setDeptName(sysDeptMapper.selectById(resUser.getDeptId()).getDeptName());
            loginUser.setRole(sysRole.getRoleName());
            loginUser.setRoleId(sysRole.getId());
            loginUser.setMenus(MenuUtil.getMenuTree(sysUserMapper.selectUserMenus(resUser.getId()).stream().filter(m -> m.getType() == 1).collect(Collectors.toList())));
            //loginUser.setPermissionList(sysUserMapper.getPermissionListByUserId(sysUser.getId()));
            return loginUser;
        }
        else
            return null;

    }

    @Override
    public List<SysUserDto> getList(SysUser sysUser) {
        return sysUserMapper.selectUserDtoList(sysUser);
    }

    @Override
    public List<SysUser> getLeaderList(SysUserDto sysUserDto) {
        return sysUserMapper.getLeaderList(sysUserDto);
    }

    @Override
    @Transactional
    public Integer add(SysUserVO sysUserVO) {
        if (sysUserMapper.selectList(Wrappers.<SysUser>lambdaQuery()
                .eq(true, SysUser::getUserName, sysUserVO.getUserName())
                .eq(SysUser::getType, SysUserTypeEnums.USER.getCode())).size() > 0
        ) {//用户名已存在
            return 0;
        }
        sysUserMapper.insert(sysUserVO);
        if (sysUserVO.getRoleId() != null) {

//            for (Integer roleId : sysUserVO.getRoleId()) {
                SysUserRole sysUserRole = new SysUserRole();
                sysUserRole.setUserId(sysUserVO.getId());
                sysUserRole.setRoleId(sysUserVO.getRoleId());
                sysUserRoleMapper.insert(sysUserRole);
//            }
        }

        return 1;
    }

    @Override
    @Transactional
    public Integer update(SysUserVO sysUserVO) {
        sysUserRoleMapper.delete(Wrappers.<SysUserRole>lambdaQuery()
                .eq(true,SysUserRole::getUserId,sysUserVO.getId()));
        sysUserMapper.updateById(sysUserVO);

//        log.info(String.valueOf(sysUserVO.getRoleIds()));
        if (sysUserVO.getRoleId() != null) {
//            for (Integer roleId : sysUserVO.getRoleIds()) {
                SysUserRole sysUserRole = new SysUserRole();
                sysUserRole.setUserId(sysUserVO.getId());
                sysUserRole.setRoleId(sysUserVO.getRoleId());
                sysUserRoleMapper.insert(sysUserRole);
//            }

//                SysUserRole sysUserRole = new SysUserRole();
//                sysUserRole.setUserId(sysUserVO.getId());
//                sysUserRole.setRoleId(sysUserVO.getRoleIds());
//                i = sysUserRoleMapper.insert(sysUserRole);

        }
        return 1;
    }

    @Override
    public Integer delete(Integer id) {
        return sysUserMapper.deleteById(id);
    }

    @Override
    public Integer deleteMult(List<Integer> ids) {
        return sysUserMapper.deleteBatchIds(ids);
    }

    @Override
    public Integer changeState(Integer id, Integer state) {
        int i = sysUserMapper.changeState(id,state);
        return i;
    }

    @Override
    public void exportExcel(SysUser sysUser,ServletOutputStream outputStream) {
        //查询
        List<SysUserDto> list=sysUserMapper.selectUserDtoList(sysUser);
        //生成
        EasyExcel.write(outputStream, SysUserDto.class).sheet().doWrite(list);
    }

    @Override
    public R importExcel(InputStream inputStream) {
        //.解析
        List<UserExcel> list=EasyExcel.read(inputStream, UserExcel.class,null).sheet().doReadSync();
        List<SysUserRole> userRoles=new ArrayList<>();
        List<UserExcel> result=new ArrayList<>();
        list.forEach(u->{
            SysUser user= EntityConvertUtil.convert(u,SysUser.class);
            if(sysUserMapper.insert(user)>0){
                SysUserRole sysUserRole = new SysUserRole();
                sysUserRole.setUserId(user.getId());
                sysUserRole.setRoleId(u.getRoleId());
                userRoles.add(sysUserRole);
            }else {
                result.add(u);
            }
        });
        //用户 角色
        sysUserMapper.insertRolesBatch(userRoles);
        if(result.size()==0){
            return R.ok("导入成功");
        }else {
            return R.error(result);
        }
    }
    @Override
    public R getEmpList(EmpPage empPage) {
        LambdaQueryWrapper<SysUser> wrapper = new LambdaQueryWrapper<>();

        if (StringUtils.isNotBlank(empPage.getEmpName())) {
            wrapper.like(SysUser::getEmpName, empPage.getEmpName());
        }
        if (StringUtils.isNotBlank(empPage.getWorkCode())) {
            wrapper.eq(SysUser::getWorkCode, empPage.getWorkCode());
        }
        wrapper.eq(SysUser::getType, SysUserTypeEnums.EMP.getCode());
        return R.ok(sysUserMapper.selectPage(new Page<>(empPage.getPageNum(), empPage.getPageSize()), wrapper));
    }

    @Override
    public R getById(Integer id) {
        SysUser sysUser = sysUserMapper.selectById(id);
        if (Objects.isNull(sysUser)) {
            return R.error("查询失败");
        }
        return R.ok(sysUser);
    }

    @Override
    public R<String> add(EmpAdd empAdd) {
        // 查询部门信息
        LambdaQueryWrapper<SysDept> deptWrapper = new LambdaQueryWrapper<>();
        deptWrapper.eq(SysDept::getDeptName, empAdd.getDeptName());
        SysDept sysDept = sysDeptMapper.selectOne(deptWrapper);

        SysUser sysUser = EntityConvertUtil.convert(empAdd, SysUser.class);
        if (Objects.isNull(sysUser)) {
            return R.error("内部错误");
        }
        sysUser.setType(SysUserTypeEnums.EMP.getCode());
        sysUser.setDeptId(sysDept.getId());
        if (sysUserMapper.insert(sysUser) > 0) {
            return R.ok("新增成功");
        }
        return R.error("新增失败");

    }
}
